home *** CD-ROM | disk | FTP | other *** search
/ C/C++ Users Group Library 1996 July / C-C++ Users Group Library July 1996.iso / vol_300 / 359_09 / patch4.000 / LIB_MCOUNT.C < prev    next >
C/C++ Source or Header  |  1991-07-21  |  2KB  |  121 lines

  1. #include <fcntl.h>
  2.  
  3. typedef struct {
  4.   long low;
  5.   long high;
  6.   long nbytes;
  7. } header;
  8.  
  9. typedef struct {
  10.     unsigned long from;
  11.     unsigned long to;
  12.     unsigned long count;
  13. } MTABE;
  14.  
  15. typedef struct MTAB {
  16.   MTABE calls[341];
  17.   struct MTAB *prev;
  18. } MTAB;
  19.  
  20. static header h;
  21. short *histogram asm("mcount_histogram");
  22. short mcount_skip asm("mcount_skip");
  23. static int histlen;
  24. static MTAB *mtab=0;
  25.  
  26. void mcount(_to)
  27. {
  28.   MTAB *m;
  29.   int i;
  30.   int to;
  31.   int ebp;
  32.   int from;
  33.   int mtabi;
  34.   MTABE **cache;
  35.  
  36.   mcount_skip = 1;
  37.   asm("movl %%edx,%0" : "=g" (cache));
  38.   to = *((&_to)-1) - 13;
  39.   ebp = *((&_to)-2);
  40.   from = ((int *)ebp)[1];
  41.   if (*cache && ((*cache)->from == from) && ((*cache)->to == to))
  42.   {
  43.     (*cache)->count++;
  44.     mcount_skip = 0;
  45.     return;
  46.   }
  47.   mtabi = -1;
  48.   for (m=mtab; m; m=m->prev)
  49.   {
  50.     for (i=0; i<341; i++)
  51.     {
  52.       if (m->calls[i].from == 0)
  53.       {
  54.         mtabi = i;
  55.         break;
  56.       }
  57.       if ((m->calls[i].from == from) &&
  58.           (m->calls[i].to == to))
  59.         {
  60.           m->calls[i].count ++;
  61.           *cache = m->calls + i;
  62.           mcount_skip = 0;
  63.           return;
  64.         }
  65.     }
  66.   }
  67.   if (mtabi != -1)
  68.   {
  69.     mtab->calls[mtabi].from = from;
  70.     mtab->calls[mtabi].to = to;
  71.     mtab->calls[mtabi].count = 1;
  72.     *cache = mtab->calls + mtabi;
  73.     mcount_skip = 0;
  74.     return;
  75.   }
  76.   m = (MTAB *)sbrk(sizeof(MTAB));
  77.   m->prev = mtab;
  78.   mtab = m;
  79.   memset(m, 0, sizeof(MTAB));
  80.   m->calls[0].from = from;
  81.   m->calls[0].to = to;
  82.   m->calls[0].count = 1;
  83.   *cache = m->calls;
  84.   mcount_skip = 0;
  85. }
  86.  
  87. extern int etext;
  88.  
  89. extern void mcount_isr_init() asm("mcount_isr_init");
  90. extern void mcount_init() asm("mcount_init");
  91. void mcount_init()
  92. {
  93.   int hs;
  94.   h.low = 0x1020;
  95.   h.high = (int)&etext;
  96.   histlen = (h.high-h.low)/4*sizeof(short);
  97.   h.nbytes = sizeof(header) + histlen;
  98.   histogram = (short *)sbrk(histlen);
  99.   memset(histogram, 0, histlen);
  100.   mcount_isr_init();
  101. }
  102.  
  103. extern void mcount_write() asm("mcount_write");
  104. void mcount_write()
  105. {
  106.   MTAB *m;
  107.   int i, f;
  108.  
  109.   f = open("gmon.out", O_WRONLY|O_CREAT|O_TRUNC|O_BINARY, 0666);
  110.   write(f, &h, sizeof(header));
  111.   write(f, histogram, histlen);
  112.   for (m=mtab; m; m=m->prev)
  113.   {
  114.     for (i=0; i<341; i++)
  115.       if (m->calls[i].from == 0)
  116.         break;
  117.     write(f, m->calls, i*12);
  118.   }
  119.   close(f);
  120. }
  121.